package com.chinatgl.latte.net;

import android.app.Activity;
import android.content.Context;
import android.os.AsyncTask;
import android.text.TextUtils;
import android.util.Log;


import com.chinatgl.latte.app.Latte;
import com.chinatgl.latte.net.callback.IError;
import com.chinatgl.latte.net.callback.IFailure;
import com.chinatgl.latte.net.callback.ISuccess;
import com.chinatgl.latte.net.listener.onNetRquestListener;
import com.chinatgl.latte.net.rx.RxRestClient;
import com.chinatgl.latte.net.rx.RxRestClientBuilder;
import com.chinatgl.latte.ui.LatteLoader;
import com.chinatgl.latte.util.json.JsonUtil;


import java.io.BufferedReader;
import java.io.BufferedWriter;
import java.io.File;
import java.io.FileNotFoundException;
import java.io.FileReader;
import java.io.FileWriter;
import java.io.IOException;
import java.lang.reflect.Type;
import java.net.URLEncoder;
import java.util.WeakHashMap;

import io.reactivex.Observable;
import io.reactivex.Observer;
import io.reactivex.android.schedulers.AndroidSchedulers;
import io.reactivex.annotations.NonNull;
import io.reactivex.disposables.Disposable;
import io.reactivex.schedulers.Schedulers;

/**
 * 文件描述:
 * 作者: Created by 杨伟乔 on 2017/8/8 0008.
 * 版本号: 1.0
 */
@SuppressWarnings("all")
public class NetRequest {
    static Context context;

    public static void post(final String url, final WeakHashMap map, final Type type, boolean isCache, long cacheTimes, final onNetRquestListener listener, Activity activity) {

        context = activity;
        Log.e("网络请求的地址", url);
        Log.e("网络请求的参数", JsonUtil.parseMapToJson(map));
        /**
         * 判断是否做缓存
         * */

        if (isCache) {
            /** 做缓存  */
         /*
         * 创建url缓存地址
         */
            final String cacheFileName = creatCacheFileName(url, map);
             /*
         * 判断是否有缓存文件
         */

            File cacheFile = getCacheFile(cacheFileName);
           /*
           判断缓存是否有效
            */

            boolean isused = isUsed(cacheFile, cacheTimes);

            if (isused) {//true为有效
                /**
                 * 从缓存文件中读取数据
                 */
                getDataFromCache(url, cacheFile, type, listener);
            } else {

                /**
                 * 缓存文件失效了 过了有效期
                 */

                //访问网络代码 (核心方法)
                request(cacheFileName, url, map, type, listener);  //第一个参数是缓存的文件名字 访问后还是要继续缓存的

            }

        } else {
            /** 数据不需要缓存  */
            /**
             * 从网络中请求数据 缓存数据
             */
            request(null, url, map, type, listener);
        }

    }

    static void request(final String cacheFileName, final String url, WeakHashMap map, final Type type, final onNetRquestListener listener) {
//        RestClient.builder()
//                .url(url)
//                .params(map)
//                .loader(context)
//                .success(new ISuccess() {
//                    @Override
//                    public void onSuccess(String json) {
//                        Log.e("网络请求的结果", json);
//                        if (type == null) {
//                            //直接返回json
//                            listener.requestdataFinish(url, json);
//                        } else {
//                            /**
//                             *发送之前判断数据 如果json格式错误 或者是class传递的错误 解析的bean是null
//                             */
//                            Object bean = JsonUtil.parseJsonToBean(json, type);
//                            if (bean == null) {
//                                listener.requestdataFinish(url, json);
//
//                            } else {
//                                Log.e("网络请求结束", "服务器数据读取成功");
//
//
//                                listener.requestdataFinish(url, bean);
//                            }
//                        }
//
//                        //判断是否做缓存
//                        /**
//                         * 请求完数据之后 做数据的缓存判断
//                         */
//
//                        if (null != cacheFileName) { //判断需要缓存的文件名字
//                            /**需要缓存 */
//                            cacheData(json, cacheFileName);
//                        }
//                    }
//                })
//                .fail(new IFailure() {
//                    @Override
//                    public void onFailure() {
//                        listener.requestdataFailed(url, null);
//
//                    }
//                })
//                .error(new IError() {
//                    @Override
//                    public void onError(int code, String msg) {
//
//                        listener.requestdataFailed(url + code + msg, null);
//                    }
//                })
//
//                .build()
//                .post();



        RxRestClient.builder()
                .url(url)
                .params(map)
                .loader(context)
                .build()
                .post()
//        final Observable<String> observable = RestCreator.getRxRestService().post(url, map);
//
//        observable.
                .subscribeOn(Schedulers.io())
                .observeOn(AndroidSchedulers.mainThread())
                .subscribe(new Observer<String>() {
                    @Override
                    public void onSubscribe(@NonNull Disposable d) {

                    }

                    @Override
                    public void onNext(@NonNull String json) {

                        Log.e("网络请求的结果", json);
                        if (type == null) {
                            //直接返回json
                            listener.requestdataFinish(url, json);
                        } else {
                            /**
                             *发送之前判断数据 如果json格式错误 或者是class传递的错误 解析的bean是null
                             */
                            Object bean = JsonUtil.parseJsonToBean(json, type);
                            if (bean == null) {
                                listener.requestdataFinish(url, json);

                            } else {
                                Log.e("网络请求结束", "服务器数据读取成功");


                                listener.requestdataFinish(url, bean);
                            }
                        }

                        //判断是否做缓存
                        /**
                         * 请求完数据之后 做数据的缓存判断
                         */

                        if (null != cacheFileName) { //判断需要缓存的文件名字
                            /**需要缓存 */
                            cacheData(json, cacheFileName);
                        }

                    }

                    @Override
                    public void onError(@NonNull Throwable e) {
                        LatteLoader.stopLoading();
                        listener.requestdataFailed(url, e);

                    }

                    @Override
                    public void onComplete() {
                        LatteLoader.stopLoading();
                        listener.requestComplete();
                    }
                });


    }

    /**
     * 缓存数据 参数是 xml字符串
     *
     * @param result   json数据缓存
     * @param fileName 文件名称
     */
    static void cacheData(String result, String fileName) {
        if (TextUtils.isEmpty(result)) {
            //如果 数据为空,返回,不再继续缓存
            return;
        }

        //根据文件名获取
        File cacheFile = getCacheFile(fileName);
        BufferedWriter writer = null;
        try {

            //写入缓存
            writer = new BufferedWriter(new FileWriter(cacheFile));
            writer.write(result);
            writer.flush(); //刷新进去数据

        } catch (IOException e) {
            e.printStackTrace();
        } finally {


        }


    }

    /**
     * 创建缓存文件的名称
     *
     * @param catalog 类型
     * @param values  参数
     * @return 拼接完成的文件名称
     */
    static String creatCacheFileName(String catalog, WeakHashMap values) {

        /**根据传入进来的参数创建缓存文件名字*/
        if (values == null) {

            return catalog;
        } else {
            return catalog + JsonUtil.parseBeanToJson(values);
        }

    }

    /**
     * 获取缓存文件
     *
     * @param cacheFileName 根据文件名字去获取文件
     * @return file
     */
    static File getCacheFile(String cacheFileName) {

        try {
            // 进行编码
            cacheFileName = URLEncoder.encode(cacheFileName, "utf-8");
//返回缓存文件
            return new File(Latte.getApplication().getCacheDir(), cacheFileName);


        } catch (Exception e) {

            e.printStackTrace();
        }

        return null;
    }


    /**
     * 判断缓存文件是否有效
     *
     * @param cacheFile 缓存的文件
     * @return boolean
     */
    static boolean isUsed(File cacheFile, long isUsedTime) {

        //判断缓存文件是否有效,

        /**
         1.首先判断文件是否为null 或者是不存在的
         */
        if (cacheFile == null || !cacheFile.exists()) {
            //条件满足一个 就返回false

            return false; //文件不存在
        }
        /**
         2. 判断文件存在的情况
         */
        //定义文件的有效

        /** 获取文件最后的修改时间 */
        long modified = cacheFile.lastModified();
        /** 获取系统的当前的时间 */
        long millis = System.currentTimeMillis();
        /** 计算系统当前的时间和文件最后修改时间的差值 */
        long times = millis - modified;
        /** 如果有效时间 大于 差值 返回true 证明文件有效 */
        return isUsedTime * 1000 * 60 > times;


    }


    /**
     * 从缓存文件中获取数据
     *
     * @param cacheFile 缓存文件
     * @param listener  获取数据后实现接口然后可以获取数据
     */
    static void getDataFromCache(final String catalog, final File cacheFile, final Type type, final onNetRquestListener listener) {


        //读取缓存文件
        new AsyncTask<Void, Void, String>() {
            /**在子线程操作的方法**/
            @Override
            protected String doInBackground(Void... params) {
                BufferedReader reader;
//读取文件的方法  不解释
                try {
                    reader = new BufferedReader(new FileReader(cacheFile));

                    String line;
                    StringBuilder sb = new StringBuilder();
                    try {
                        while ((line = reader.readLine()) != null) {

                            sb.append(line).append("\n");
                        }
                        String json = sb.toString();

                        reader.close();
                        //返回json
                        return json;
                    } catch (IOException e) {
                        e.printStackTrace();
                    }

                } catch (FileNotFoundException e) {
                    e.printStackTrace();
                }

                return null;
            }

            /**
             * 执行的结果  通过这个方法获取上面的方法执行的结果
             * @param result
             */
            @Override
            protected void onPostExecute(String result) {
                super.onPostExecute(result);
                //这里的参数是上面的那个方法返回的数据
//这里我们直接把json解析出来  返回为一个bean对象
                if (type == null) {
                    //不需要解析  直接传递json回去
                    listener.requestdataFinish(catalog, result);
                } else {
                    Object bean = JsonUtil.parseJsonToBean(result, type);
                    //解析好的结果 我们需要判断
                    if (bean != null) {
                        //如果传递的class文件是错误的或者json是错误的 不能解析
                        //把数据传递给调用者
                        Log.e("网络请求结束", "缓存数据读取成功");
                        listener.requestdataFinish(catalog, bean);
                    } else {
                        //传递json回去
                        listener.requestdataFinish(catalog, result);
                    }
                }
            }

        }.execute();


    }
}
